iT邦幫忙

2022 iThome 鐵人賽

DAY 13
0
Modern Web

一探紅寶石的神秘面紗 - Ruby 及 Rails入門介紹 系列系列 第 13

Day 13 - 掌握Ruby世界就要先懂:模組 Module

  • 分享至 

  • xImage
  •  

這篇就來好好了解一下 Ruby 中的模組吧,先來用個我最愛的超級英雄蜘蛛人當成例子
以前面人類類別的例子,我希望他可以有吐絲的能力來當蜘蛛人,可能會想用以下這些做法:

  1. 建立一個蜘蛛類別並且帶有吐絲功能,然後再叫人類類別去繼承
  2. 在人類類別裡面定義一個吐絲功能

第1種的方式感覺在邏輯上比較奇怪,人為了吐絲就要去繼承蜘蛛,感覺就跟原本設定的類別有點衝突;第2種是直接寫在內部確實也可以達到同樣效果,但如果其他類別也需要用到這項能力就要另外在寫,沒辦法抽出來共用。

如果我們能夠把這些超級能力抽出來,需要使用再引入,不是很好嗎?
於是就有了模組的概念可以來解決這樣的狀況!

模組定義與使用

module 後面接上模組名稱,命名規則與 class 相同,使用駝峰大寫,下面就可以定義內部要有的方法。
如果在其他類別內要引用就使用 include

# 定義吐司模組
module spinning
  def spin
    puts "我會吐絲啦!"
  end
end

# 引入模組到人類類別
class Human
  include spinning # 引入吐絲模組
end

Sean = Human.new
Sean.spinning # 我會吐絲啦!

在類別中引入模組就可以讓新建立的實體 Sean 直接可以使用模組內的方法了。

class Dog
  include spinning 
end

如果建立一個狗類別也想要使用只要引入他也可以有這項能力。

類別和模組的差別?

在 Ruby 裡,「類別」的上層類別就是「模組」,也可以算是一種類別。
可以進入 irb 透過 supercalss 來看到 Class 的上層就是 Module

3.1.2 :001 > Class.superclass
 => Module 

比較兩者的差異:
在 irb 中類別及模組後面加上.instance_methods,就可以查到所有內部具有的實體方法,將兩者相減可以知道差異

3.1.2 :002 > Class.instance_methods - Module.instance_methods
 => [:allocate, :superclass, :subclasses, :new]

下層的 Class 類別,比 Module 類別多了 4 個方法,其中 allocate 及 new 造就以下的差異:

  • 模組沒辦法 new 一個新的實體出來 (new)。
  • 模組沒辦法繼承別的模組 (allocate)。

如何選擇用類別繼承還是模組?

如果你發現你要使用功能,可能在很多不同體系的類別裡都會用得到,那你可以考慮把功能寫在模組裡,需要的時候再 include 進來。


  1. 為你自己學 Ruby on Rails
  2. [Ruby] 物件(object)、類別(class)和模組(module)

上一篇
Day 12 - 掌握Ruby世界就要先懂:類別 Class
下一篇
Day 14 - 進入Rails世界必須懂:MVC 是甚麼?
系列文
一探紅寶石的神秘面紗 - Ruby 及 Rails入門介紹 系列30
圖片
  直播研討會
圖片
{{ item.channelVendor }} {{ item.webinarstarted }} |
{{ formatDate(item.duration) }}
直播中

尚未有邦友留言

立即登入留言